import { expect } from '@jest/globals';
import * as fse from 'fs-extra';
import fsExtra from 'fs-extra';
import JSON5 from 'json5';
import path from 'path';

import { initExecuteCommand, runHvigorAsync } from '../../common/common';
import {
  AbilityType,
  APIType,
  APIVersion, CaseLevel, IsEnable,
  LanguageType, ModuleTemplateType,
  RuntimeOSType,
  SDKType
} from '../../plugins/project-builder/models/constants';
import { TestCaseBuilder } from '../../plugins/task-builder/task-case-builder';
import { ProjectBuildOption, TestCaseFun } from '../../plugins/task-builder/test-case';
import { TestTaskOptionBuilder } from '../../plugins/task-builder/test-task-option';

const projectBuilderOption: ProjectBuildOption = {
  template: {
    sdk: SDKType.Single,
    runtimeOS: RuntimeOSType.HarmonyOS,
    apiVersion: APIVersion.API11,
    apiType: APIType.STAGE,
    language: LanguageType.ArkTs,
    abilityType: AbilityType.Application,
    entryTemplateType: ModuleTemplateType.EmptyAbility
  },
  modulesOption: {
    [ModuleTemplateType.FeatureEmptyAbility]: 1,
  }
};

const testFun: TestCaseFun = async (project, taskConfig, record) => {
  const commandsHap = initExecuteCommand({
    mode: 'module',
    module: 'entry@mini,feature@mini',
    product: 'default2',
    tasks: 'assembleHap'
  });

  const projectBuildProfilePath = path.resolve(project.projectRootPath(), 'build-profile.json5');
  const fileData = await fse.readFile(projectBuildProfilePath);
  const buildProfileObj = JSON5.parse(fileData.toString());
  buildProfileObj.app.products.push({
    'name': 'default2',
    'signingConfig': 'default',
    'compatibleSdkVersion': '5.0.0(12)',
    'runtimeOS': 'HarmonyOS',
  });
  buildProfileObj.modules.forEach((moduleTargetOpt: any) => {
    moduleTargetOpt.targets.push({
      'name': 'mini',
      'applyToProducts': [
        'default2'
      ]
    });
  });
  await fse.writeJson(projectBuildProfilePath, buildProfileObj, { spaces: 2 });

  const entryModulePath = project.getModule('entry').moduleRootPath();
  const featureModulePath = project.getModule('feature').moduleRootPath();
  await addTargetToModule(entryModulePath,'mini');
  await addTargetToModule(featureModulePath,'mini');

  const result = await runHvigorAsync(project.projectRootPath(), commandsHap);
  expect(result.stdout).toContain('BUILD SUCCESSFUL');

  const entryHapPath = path.resolve(entryModulePath, 'build', 'default2', 'outputs', 'mini', 'entry-mini-unsigned.hap');
  const featureHapPath = path.resolve(featureModulePath, 'build', 'default2', 'outputs', 'mini', 'feature-mini-unsigned.hap');
  const existsEntryHapPath = await fse.pathExists(entryHapPath);
  const existsFeatureHapPath = await fse.pathExists(featureHapPath);
  expect(existsEntryHapPath).toBe(true);
  expect(existsFeatureHapPath).toBe(true);
};

async function addTargetToModule(modulePath: string,targetName:string) {
  const buffer = await fsExtra.readFile(path.resolve(modulePath, 'build-profile.json5'));
  const parse = JSON5.parse(buffer.toString());
  parse.targets.push({
    'name': targetName
  });
  await fsExtra.writeFile(path.resolve(modulePath, 'build-profile.json5'), JSON5.stringify(parse, null, 2));
}

TestCaseBuilder.builder()
  .caseName('OPENLAB_AIDE_ZOS_Build_product_target_06_004')
  .description(
    '1、新建Stage模型eTS工程，新增feature模块，在工程build-profile.json5添加新的product："name": "default2"\n' +
    '2、在各模块build-profile.json5添加新的target："name": "mini"，在工程build-profile中添加新增target-mini 关联-"applyToProducts"添加"default2"\n' +
    '3、命令行执行./hvigorw assembleHap -p product=default2 -p module="entry@mini,feature@mini"')
  .projectBuilderOption(projectBuilderOption)
  .taskConfig(TestTaskOptionBuilder.builder().caseLevel(CaseLevel.L1).ohpmInstall(IsEnable.Enable).build())
  .testFun(testFun)
  .load();